// ./app.js (错误处理中间件部分)

const logger = require('../config/logger.config'); // 引入 logger
const { sendAlert } = require('../utils/alerter.util');
const { CustomError } = require('../utils/CustomError');

// ... (所有路由和中间件之后)
/**
 * 统一错误处理中间件 (必须有四个参数)
 */
const errorHandler = (err, req, res, next) => {
    // 默认状态码为 500，默认消息
    let status = 500;
    let message = '服务器内部错误';
    let isProductionError = false;

    // ----------------------------------------------------
    // A. 处理自定义错误 (如 400, 401, 404)
    // ----------------------------------------------------
    if (err instanceof CustomError) {
        status = err.status;
        message = err.message;
    }
    // B. 处理 Mongoose 验证错误
    else if (err.name === 'ValidationError') {
        status = 400;
        message = Object.values(err.errors)
            .map((val) => val.message)
            .join('; ');
    }
    // C. 处理 JWT 认证错误 (如 Token 过期或无效)
    else if (err.name === 'JsonWebTokenError' || err.name === 'TokenExpiredError') {
        status = 401;
        message = '认证失败：Token 无效或已过期';
    }
    // D. 处理 Multer 文件上传错误
    else if (err.name === 'MulterError') {
        status = 400;
        message = `文件上传错误: ${err.message}`;
    }
    // E. 处理未预期的系统级错误 (500)
    else {
        status = err.status || 500;
        message = err.message || '服务器内部错误';
        isProductionError = true; // 标记为需要告警的错误
    }

    // ----------------------------------------------------
    // 记录日志和发送告警
    // ----------------------------------------------------

    // 1. 记录日志 (所有 5xx 错误都以 error 级别记录)
    if (status >= 500) {
        logger.error(`系统错误 (${status})`, {
            path: req.originalUrl,
            method: req.method,
            ip: req.ip,
            error_message: err.message,
            stack: err.stack, // 记录堆栈方便排查
        });

        // 2. 生产环境下的 500 错误发送实时告警
        if (isProductionError && process.env.NODE_ENV === 'production') {
            const alertSubject = `E500: ${req.method} ${req.originalUrl}`;
            const alertText = `
                请求路径: ${req.method} ${req.originalUrl}
                用户ID: ${req.user ? req.user.id : 'N/A'}
                时间: ${new Date().toISOString()}
                错误消息: ${err.message}
                错误堆栈: ${err.stack}
            `;
            sendAlert(alertSubject, alertText);
        }
    } else {
        // 记录非 5xx 错误，通常为 warn 或 info
        logger.warn(`业务错误 (${status})`, { message: err.message, path: req.originalUrl });
    }

    // ----------------------------------------------------
    // 返回客户端响应
    // ----------------------------------------------------
    res.status(status).send({
        success: false,
        status: status,
        message: message,
        // 非生产环境才返回堆栈，方便调试
        stack: process.env.NODE_ENV !== 'production' ? err.stack : undefined,
    });
};

module.exports = errorHandler;
